package uk.ljmu.qudexapps.swfspreadsheet.utilities;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URL;
import java.util.LinkedList;
import java.util.List;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;

import org.springframework.web.multipart.MultipartFile;

public class GeneralUtilities {
	   private final static int BUFFER = 2048;
	    private static String fileSeparator = System.getProperty("file.separator");

	    public static void createFile(String fileName, InputStream input)
		    throws IOException {
		InputStream inputStream = null;
		OutputStream out = null;
		try {
		    File f = new File(fileName);
		    inputStream = input;
		    out = new FileOutputStream(f);
		    byte buf[] = new byte[1024];
		    int len;
		    while ((len = inputStream.read(buf)) > 0)
			out.write(buf, 0, len);
		    out.close();
		    inputStream.close();
		} finally {
		    if (out != null)
			out.close();
		    if (inputStream != null)
			inputStream.close();
		}
	    }

	    /**
	     * @throws IOException
	     * 
	     */
	    public static void copyFile(String filePath, String serverFolder)
		    throws IOException {
		InputStream outputFile = null;
		FileOutputStream out = null;
		try {
		    File inputFile = new File(filePath);
		    URL copyurl;
		    copyurl = new URL(serverFolder);
		    outputFile = copyurl.openStream();
		    out = new FileOutputStream(inputFile);
		    int c;
		    while ((c = outputFile.read()) != -1)
			out.write(c);
		    outputFile.close();
		    out.close();
		} finally {
		    if (outputFile != null)
			outputFile.close();
		    if (out != null)
			out.close();
		}
	    }

	    /**
	     * 
	     * @param serverPath
	     * @param zipFile
	     * @return
	     * @throws IOException
	     * @throws Exception
	     */
	    public static boolean decompressZipFile(String serverPath,
		    List<MultipartFile> zipFiles) throws IOException {
		BufferedOutputStream dest = null;
		ZipInputStream zis = null;
		try {
		    for (MultipartFile zfile : zipFiles) {
		    	if (zfile.getSize() <= Constants.FILE_MAX_MEM_SIZE) {
		    		zis = new ZipInputStream(new BufferedInputStream(zfile
		    				.getInputStream()));
		    	} else {
		    		zis = new ZipInputStream(new FileInputStream(new File(serverPath + System.getProperty("file.separator") + zfile.getOriginalFilename())));
		    	}
			ZipEntry entry;
			while ((entry = zis.getNextEntry()) != null) {
			    int count;
			    byte data[] = new byte[BUFFER];
			    // GET REAL PATH
			    String completeUrl = (serverPath.endsWith(fileSeparator)) ? serverPath
				    + entry.getName()
				    : serverPath + fileSeparator + entry.getName();

			    if (entry.isDirectory()) {
				boolean dirCreated = new File(completeUrl).mkdir();
				if (dirCreated)
				    continue;
				else
				    return false;
			    }
			    // write the files to the disk
			    FileOutputStream fos = new FileOutputStream(completeUrl);

			    dest = new BufferedOutputStream(fos, BUFFER);
			    while ((count = zis.read(data, 0, BUFFER)) != -1) {
				dest.write(data, 0, count);
			    }
			    dest.flush();
			}
		    }
		    return true;
		} finally {
		    if (dest != null)
			dest.close();
		    if (zis != null)
			zis.close();
		}
	    }

	    /**
	     * Reverse the split operation.
	     * 
	     * @param parts
	     *            The parts to combine
	     * @param index
	     *            the index to the fist part to use
	     * @param length
	     *            the number of parts to use
	     * @param splitter
	     *            The between-parts text
	     */
	    public static String unsplit(String[] parts, int index, int length,
		    String splitter) {
		if (parts == null)
		    return null;
		if ((index < 0) || (index >= parts.length))
		    return null;
		if (index + length > parts.length)
		    return null;

		StringBuilder buf = new StringBuilder();
		for (int i = index; i < index + length; i++) {
		    if (parts[i] != null)
			buf.append(parts[i]);
		    buf.append(splitter);
		}

		// remove the trailing splitter
		buf.setLength(buf.length() - splitter.length());
		return buf.toString();
	    }

	    /**
	     * 
	     * @param input
	     * @param deleteMe
	     * @return
	     */
	    public static List<String> removeElements(String[] input, String deleteMe) {
		List<String> result = new LinkedList<String>();
		for (String item : input)
		    if (!deleteMe.equalsIgnoreCase(item))
			result.add(item);
		return result;
	    }

	    static public boolean deleteDirectory(File path) {
		if (path.exists()) {
		    File[] files = path.listFiles();
		    for (int i = 0; i < files.length; i++) {
			if (files[i].isDirectory()) {
			    deleteDirectory(files[i]);
			} else {
			    files[i].delete();
			}
		    }
		}
		return (path.delete());
	    }
}
